package com.kylin.common.core.annotation.aspect;

import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.JSONObject;
import com.kylin.common.core.annotation.Rsa;
import com.kylin.common.core.beans.GlobalResultCode;
import com.kylin.common.core.exception.ServiceException;
import com.kylin.common.core.filter.ApiLogExtend;
import com.kylin.common.core.filter.ApiLogThreadLocal;
import com.kylin.common.core.util.RSACoder;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;
import org.aspectj.lang.reflect.MethodSignature;
import org.springframework.stereotype.Component;
import org.springframework.web.context.request.RequestAttributes;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import javax.servlet.http.HttpServletRequest;
import java.lang.reflect.Method;
import java.nio.charset.StandardCharsets;

/**
 * Rsa参数加密，切面处理类
 *
 * @author wuhao
 * @version 1.0 - 2019/6/24
 */
@Aspect
@Component
public class RsaAspect {
	/**
	 * RSA私钥
	 */
//	private String privateKey = "MIIBUwIBADANBgkqhkiG9w0BAQEFAASCAT0wggE5AgEAAkEA0vfvyTdGJkdbHkB8\n" +
//			"mp0f3FE0GYP3AYPaJF7jUd1M0XxFSE2ceK3k2kw20YvQ09NJKk+OMjWQl9WitG9p\n" +
//					"B6tSCQIDAQABAkA2SimBrWC2/wvauBuYqjCFwLvYiRYqZKThUS3MZlebXJiLB+Ue\n" +
//					"/gUifAAKIg1avttUZsHBHrop4qfJCwAI0+YRAiEA+W3NK/RaXtnRqmoUUkb59zsZ\n" +
//					"UBLpvZgQPfj1MhyHDz0CIQDYhsAhPJ3mgS64NbUZmGWuuNKp5coY2GIj/zYDMJp6\n" +
//					"vQIgUueLFXv/eZ1ekgz2Oi67MNCk5jeTF2BurZqNLR3MSmUCIFT3Q6uHMtsB9Eha\n" +
//					"4u7hS31tj1UWE+D+ADzp59MGnoftAiBeHT7gDMuqeJHPL4b+kC+gzV4FGTfhR9q3\n" +
//					"tTbklZkD2A==";
			// 公钥
			private String publicKey = "MIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEA02HzJQU4PkGwjr9MStvG\n" +
			"3hx5PR79CjxMi3OCn+yhA4pT20f+yqAPNdjdztO75bO+eMPYUNp+MCuYMFpHWV0S\n" +
			"kYldfBb25rA5dSoUdAWoOdsZ2veN1A1fxyw6AWW8lICUeUMzdQAzoED0Cz4srD3M\n" +
			"AaNVmLX6+jEX364hDxhNB5eWUV/W9mGO0+RVcn+FM2XKm5J7iajQQ6WkQEn34tnA\n" +
			"HWDzTPauCQJFgEIFBhUCUqkWxmJ/0jMWPWAjSxntk/xX/j9I1lobJXk9dUi6iOvz\n" +
			"dTTbbZl+YJCw44Q1XVq+dqI5P4kqgH9xMvZAahW5bjbUq1ttupK6dg+YwemyBe/i\n" +
			"Fe3hMUU/lcwEM8Yc+HFB4a9RSYSQhfPUaEL3qcsAmOt4YUSQhTm3GCTsrwGZXjej\n" +
			"vV+DeEMglYY4nxTweEtN3PB71ZNUDiXd2ENbWzjJ22bFk4Je5drAGBsH5R9HTOJB\n" +
			"efXAEyrEjn3GVt6+eakysO2ckK9RnhxzDWMrUrns7mq/u1GX7I19ulDTJXFPnWK3\n" +
			"nXs4tluGDIaRizdWw4ehVwtlCuOCPIKD5yJggBJHRySGRtTRVXiZLjxUJ4zX2VnF\n" +
			"co796EnJ2tlnrZwizGLCocIXPfEC/6os0R6q7MCW/7r0Gdr2+Pq8+hYMf4XbQI0J\n" +
			"+8vVUd4kymioN3A4AZCTu0cCAwEAAQ==";

	private String privateKey = "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\n" +
			"c87c/YVWUg/cOzx87nxXu5O1QMDaTXFS";

	@Pointcut("@annotation(com.kylin.common.core.annotation.Rsa)")
	public void rsaPointCut() {
		// Do nothing because
	}

	@Around("rsaPointCut()")
	public Object around(ProceedingJoinPoint pjp) throws Throwable {

		Object[] params = pjp.getArgs();
		JSONObject rasParams = (JSONObject) params[0];

		MethodSignature methodSignature = (MethodSignature) pjp.getSignature();
		Method method = methodSignature.getMethod();
		Rsa rsa = method.getAnnotation(Rsa.class);
		if(!rsa.pass().equals(getRsaPassValue())) {

			// 是否请求时效
			if(rsa.timeCheck()) {
				Long timestamp = rasParams.getLong("timestamp");
				if(timestamp != null && (System.currentTimeMillis() - timestamp) > rsa.period()) {
					throw new ServiceException(GlobalResultCode.RSA_TIME_EXCEPTION);
				}
			}

			String info = "";
			try {
				String reqParams = rasParams.getString("reqParams").replace(" ","+");
				info = new String(RSACoder.decryptByPrivateKey(reqParams , privateKey), StandardCharsets.UTF_8);
			}catch (Exception e){
				throw new ServiceException(GlobalResultCode.RSA_KEY_EXCEPTION);
			}

			// 放入上下文对象用户接口日志统计
			ApiLogExtend apiLogExtend = ApiLogThreadLocal.getContext();
			apiLogExtend.setDecryptParams(info);
			ApiLogThreadLocal.setContext(apiLogExtend);

			params[0] = JSON.parseObject(info);
		}

		return pjp.proceed(params);
	}
	
	/** 获取头部中过滤ras校验的值 */
	private String getRsaPassValue() {
		RequestAttributes ra = RequestContextHolder.getRequestAttributes();
		ServletRequestAttributes sra = (ServletRequestAttributes)ra;
		HttpServletRequest request = sra.getRequest();
		return request.getHeader("x-rsa-pass");
	}

}
